<template>
  <div class="table-content">
    <table-search v-if="tableOptions.search" :searchOptions="searchOptions" :searchSource="searchSource"
     @searchHandle="searchHandle" @resetHandle="resetHandle">
    </table-search>
    <el-table border
      ref="multipleTable"
      v-loading="tableOptions.loading"
      :size="tableOptions.size"
      :stripe="tableOptions.stripe"
      :highlight-current-row="tableOptions.highlightCurrentRow"
      :fit="tableOptions.fit"
      :data="tableSource.data.content"
      @selection-change="selectionChangeHandle"
      @sort-change="sortChangeHandle" style="width: 100%;">

      <!-- 选择框 -->
      <el-table-column v-if="tableOptions.mutiSelect" :selectable="selectionHandle" type="selection" width="45" align="center"></el-table-column>
      <!-- 序号框 -->
      <el-table-column v-if="tableOptions.serialNumber" type="index" label="序号" align="center" fixed></el-table-column>
      <el-table-column
        v-for="(item, key) in tableSource.headers" :key="key"
        :prop="item.prop" :label="item.label" :fixed="item.fixed" :width="item.width" :min-width="item.minWidth"
        :align="item.align" :header-align="item.headerAlign" :sortable="item.sortable">

        <template slot-scope="scope">
          <!-- 操作按钮组 -->
          <div v-if="item.operation" class="column_operate">
            <div class="column_operate_group">
              <!-- 三个一排的情况 -->
              <template v-if="item.operations.length < 4">
                <template v-for="(btn, index) in item.operations">
                  <div class="column_operate_group__item" v-if="btn.show || new Set(scope.row['showButtonIndexs']).has(index)" :key="index">
                    <el-button v-prevent-re-click
                     :size="tableOptions.size" :type="btn.type" :icon="btn.icon" :plain="btn.plain"
                     :disabled="btn.disabled || new Set(scope.row['disabledButtonIndexs']).has(index)"
                     @click.native.prevent="btn.method(index, scope.row)">
                      {{ btn.label }}{{scope.row.show}}
                    </el-button>
                  </div>
                </template>
              </template>
              <!-- 四个以上的情况 -->
              <template v-else>
                <template v-for="(btn, index) in item.operations.slice(0, 2)">
                  <div class="column_operate_group__item" v-if="btn.show" :key="btn.label">
                    <el-button v-prevent-re-click
                     :size="tableOptions.size" :type="btn.type" :icon="btn.icon" :plain="btn.plain"
                     :disabled="btn.disabled || new Set(scope.row['disabledButtonIndexs']).has(index)"
                     @click.native.prevent="btn.method(index, scope.row)">
                      {{ btn.label }}
                    </el-button>
                  </div>
                </template>
                <el-dropdown class="column_operate_group__dropdown">
                  <el-button type="primary" class='iconmore pointer iconfont'>更多</el-button>
                  <el-dropdown-menu slot="dropdown">
                    <el-dropdown-item v-for="(btn, index) in item.operations.slice(2, item.operations.length)" :key="index"
                      @click.native.prevent="btn.method(index + 2, scope.row)" :disabled="new Set(scope.row['disabledButtonIndexs']).has(index + 2)">
                      {{ btn.label }}
                    </el-dropdown-item>
                  </el-dropdown-menu>
                </el-dropdown>
              </template>
            </div>
          </div>
          <div v-else>
            <a v-if="item.route" class="column_link" @click="activeHandle(scope.row, item)">
                <span v-if="!item.formatData">{{ scope.row[item.prop] }}</span>
                <span v-else>{{ item.formatData(scope.row, item, scope.row[item.prop]) }}</span>
            </a>
            <div v-else>
                <span v-if="!item.formatData">
                  <template v-if="!item.tag">
                    {{ scope.row[item.prop] }}
                  </template>
                  <template v-else>
                    <el-tag :type="item.tag.filter(scope.row[item.tag.prop || item.prop])">
                      {{ scope.row[item.prop] }}
                    </el-tag>
                  </template>
                </span>
                <span v-else>
                  <template v-if="item.tag">
                    <el-tag :type="item.tag.filter(scope.row[item.tag.prop || item.prop])">
                      {{ item.formatData(scope.row, item, scope.row[item.prop]) }}
                    </el-tag>
                  </template>
                  <template v-else>
                    {{ item.formatData(scope.row, item, scope.row[item.prop]) }}
                  </template>
                </span>
            </div>
          </div>
        </template>

      </el-table-column>

    </el-table>
    <table-pagination v-if="tableOptions.pagination && tableSource.data.totalElements !== 0"
      :total="tableSource.data.totalElements" :page="tableSource.data.page" :pageSize="tableSource.data.pageSize"
      @pageHandle="pageHandle"/>
  </div>
</template>

<script>
import TableSearch from '@/components/table/table-search'
import TablePagination from '@/components/table/table-pagination'
export default {
  name: 'table-content',
  components: { TableSearch, TablePagination },
  props: {
    // 搜索配置
    searchSource: {
      type: Object,
      default: () => ({})
    },
    // 表设置
    tableOptions: {
      type: Object,
      default: () => ({
        size: 'mini', // 表尺寸medium|small|mini
        loading: false, // 是否显示数据加载框
        stripe: false, // 是否为斑马纹 table
        highlightCurrentRow: true, // 是否要高亮当前行
        fit: true, // 列的宽度是否自撑开
        mutiSelect: true, // 是否显示选择框
        serialNumber: false, // 是否显示序号框
        search: true, // 是否搜索
        pagination: true // 是否分页
      })
    },
    // 表配置
    tableSource: {
      type: Object,
      default: () => ({
        // 表头设置
        headers: {
          type: Array,
          default: () => [{
            prop: '字段名',
            label: '列名',
            fixed: 'true', // 列是否固定在左侧或者右侧，true 表示固定在左侧
            width: '100px', // 对应列宽度
            minWidth: '100px', // 设置列的最小宽度(不传默认值)
            align: 'center', // 列内容对其方式 left/center/right
            headerAlign: 'center', // 表头对齐方式，若不设置该项，则使用表格的对齐方式 left/center/right
            sortable: 'false', // 对应列是否可以排序，如果设置为 'custom'，则代表用户希望远程排序，需要监听 Table 的 sort-change 事件 true, false, 'custom'
            tag: () => ({
              prop: '', // 标签字段
              filter: () => {} // 标签方法
            }),
            route: {
              type: 0, // 类型0弹框1路由跳转
              path: '路由地址',
              field: '取值字段',
              method: (row) => {}
            }, // 跳转
            formatData: (row, column, columnValue) => {}, // 格式化内容
            operation: true, // 是否需要操作项
            list: [{ // 操作项配置
              label: '文本',
              type: '类型', // primary / success / warning / danger / info / text
              icon: 'el-icon-delete', // 按钮图标
              show: true, // 是否显示
              plain: false, // 是否朴素按钮
              disabled: false, // 是否禁用
              permission: '', // 按钮权限
              method: (index, row) => {} // 回调方法
            }]
          }]
        },
        // 数据集
        data: {
          type: Object,
          default: () => [{
            page: 1, // 当前页
            pageSize: 10, // 每页展示条数
            totalElements: 0, // 总条数
            content: [{
              selection: true, // 该行复选框选中控制
              disabledButtonIndexs: [], // 禁用按钮下标
              showButtonIndexs: [] // 隐藏按钮下标，只支持opersions最多三个按钮
            }] // 数据
          }]
        }
      })
    }
  },
  data() {
    return {
      height: '',
      // 选中数据
      multipleSelection: [],
      // 表操作列默认值
      operation: {
        label: '操作',
        fixed: 'right',
        minWidth: '110px',
        align: 'center',
        headerAlign: 'center'
      },
      // 搜索栏配置
      searchOptions: {
        show: true,
        init: true,
        size: this.tableOptions.size
      }
    }
  },
  created() {
    this.tableSource.headers.forEach(header => {
      if (header.headerAlign === undefined) {
        header.headerAlign = 'center'
      }
      if (header.align === undefined) {
        header.align = 'center'
      }
      if (header.operation) {
        if (header.operations && header.operations.length > 0) {
          Object.assign(header, this.operation)
          // 初始化操作栏按钮默认属性
          header.operations.forEach(item => {
            if (item.plain === undefined) {
              item.plain = false
            }
            if (item.disabled === undefined) {
              item.disabled = false
            }
            if (item.show === undefined) {
              item.disabled = false
            }
          })
        } else {
          header.operation = false
        }
        if (header.operations.filter(item => item.show === true).length === 0) {
          header.operation = false
        }
      }
    })
    this.searchOptions.show = this.searchOptions.show ? this.searchSource.operations ? this.searchSource.operations.length > 0 : false : this.searchOptions.show
  },
  beforeUpdate() {
    this.tableSource.headers.forEach(header => {
      if (header.operation) {
        header.operations = header.operations.filter(item => this.isAuth(item.permission))
        if (header.operations.length === 0) {
          header.operation = false
        }
      }
    })
    this.tableSource.headers = this.tableSource.headers.filter(item => item.operation === undefined || item.operation)
  },
  methods: {
    init() {
      console.debug('table content init')
      this.$refs.multipleTable.clearSelection()
      this.$refs.multipleTable.clearSort()
      this.$refs.multipleTable.clearFilter()
    },
    selectionHandle(row, index) {
      if (row.selection === undefined) {
        return true
      }
      return row.selection
    },
    searchHandle(obj) {
      this.$emit('searchHandle', obj)
    },
    resetHandle() {
      this.init()
      this.$emit('resetHandle')
    },
    // 多选操作
    selectionChangeHandle(val) {
      this.multipleSelection = val
      this.$emit('selectionChangeHandle', { 'backData': this.multipleSelection })
    },
    // 排序
    sortChangeHandle(column) {
      this.$emit('sortChangeHandle', { 'backData': column })
    },
    // 分页导航
    pageHandle(obj) {
      this.$emit('pageHandle', { 'backData': obj })
    },
    // row:本行数据，route：要跳转的路由路径，跳转要传的参数routeId
    activeHandle(row, item) {
      let route = item.route
      let fieldValue = row[route.field ? route.field : item.prop]
      if (route.type === 0) {
        route.method(fieldValue, row)
      } else {
        this.$router.push({
          path: '/' + route.path,
          query: {
            id: fieldValue
          }
        })
      }
    }
  }
}
</script>

<style lang="scss" scoped>
.table-content {
  .column {
    &_operate {
      margin: 0 auto;
      &_group {
        display: inline-flex;
        overflow: auto;
        text-align: center;
        &__item {
          float: left;
          display: inline;
          margin: 0 5px;
        }
        &__dropdown {
          > button {
            line-height: 7px;
          }
        }
      }
    }
    &_link {
      color: #409EFF;
      cursor: pointer;
      &:hover {
        text-decoration: none;
      }
    }
  }
}
</style>
